package com.aube.interact.taste.card;

import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.animation.ValueAnimator;
import android.content.Context;
import android.util.AttributeSet;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.FrameLayout;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;

import com.aube.interact.taste.R;
import com.aube.interact.taste.controller.DataManager;
import com.aube.interact.taste.model.OptionResultModel;
import com.aube.interact.taste.model.ReportResultModel;
import com.aube.interact.taste.model.TimeLinePiece;
import com.aube.interact.taste.model.VoteData;
import com.huyn.baseframework.model.ChannelDetail;
import com.huyn.baseframework.utils.Utils;

/**
 * Created by hill on 16/12/9.
 */

public class VSViewUp extends BaseCardNew implements View.OnClickListener {
    private final String TAG = "Aube/VSViewUp";

    private VoteData mVoteData;

    private LinearLayout mRedOptionLy, mBlueOptionLy;
    private ImageView mRedOptionImg, mBlueOptionImg;
    private TextView mRedOptionName, mBlueOptionName;
    private TextView mRedOptionPercentText, mBlueOptionPercentText;
    private View mRedOptionPercentLine, mBlueOptionPercentLine;
    private ValueAnimator mRedProgressAnimator, mBlueProgressAnimator;

    private String mRedOptionServerId, mBlueOptionServerId;
    private int mRedOptionPercent, mBlueOptionPercent;
    private int mPreselectedIndex = -1;
    private int mRedProgressCurWidth, mRedProgressTgtWidth;
    private int mBlueProgressCurWidth, mBlueProgressTgtWidth;

    public VSViewUp(Context context) {
        this(context, null);
    }
    public VSViewUp(Context context, AttributeSet attrs) {
        this(context, attrs, 0);
    }
    public VSViewUp(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        mContext = context;
    }

    @Override
    public void init(final TimeLinePiece data, ChannelDetail detail) {
        super.init(data, detail);
        initView();
    }

    @Override
    protected void initView() {
        Utils.Log(TAG, "initView");
        LayoutInflater.from(getContext()).inflate(R.layout.aube_intera_layout_sdk_vsup, this);

        // basic view
        mRoot = (FrameLayout) findViewById(R.id.sdk_vsup_root);
        mOptionGp = (LinearLayout) findViewById(R.id.sdk_vsup_optiongp);
        mFoldText = (TextView) findViewById(R.id.sdk_vsup_expand);
        mCloseView = findViewById(R.id.sdk_vsup_close);
        mDivisionView = findViewById(R.id.sdk_vsup_division_line);
        mTitleText = (TextView) findViewById(R.id.sdk_vsup_titletext);
        mParticipantsText = (TextView) findViewById(R.id.sdk_vsup_people);
        mBetterCloseView = findViewById(R.id.sdk_vsup_closeclickview);

        // option related view
        mRedOptionImg = (ImageView) findViewById(R.id.sdk_vsup_optionred_img);
        mBlueOptionImg = (ImageView) findViewById(R.id.sdk_vsup_optionblue_img);
        mRedOptionName = (TextView) findViewById(R.id.sdk_vsup_optionred_name);
        mBlueOptionName = (TextView) findViewById(R.id.sdk_vsup_optionblue_name);
        mRedOptionLy = (LinearLayout) findViewById(R.id.sdk_vsup_optionred);
        mBlueOptionLy = (LinearLayout) findViewById(R.id.sdk_vsup_optionblue);
        mRedOptionPercentLine = findViewById(R.id.sdk_vsup_optionred_percentview);
        mBlueOptionPercentLine = findViewById(R.id.sdk_vsup_optionblue_percentview);
        mRedOptionPercentText = (TextView) findViewById(R.id.sdk_vsup_optionred_percenttxt);
        mBlueOptionPercentText = (TextView) findViewById(R.id.sdk_vsup_optionblue_percenttxt);

        mRedOptionLy.setOnClickListener(this);
        mBlueOptionLy.setOnClickListener(this);
        mOptionGp.setOnClickListener(this);

        mTitleText.setText(mData.title);

        super.initView();

        fillOption();
    }

    private void fillOption() {
        mPreselectedIndex = DataManager.getInstance(mContext).getIndex(mData.getRid());
        mOptionLineHeight = Utils.dip2px(mContext, 0.5f);
        mRootWidth = Utils.dip2px(mContext, 180);
        mOptionGpWidth= Utils.dip2px(mContext, 150);
        mOptionViewHeight = Utils.dip2px(mContext, 42);

        if(mData == null || mData.optionSize() == 0) return;

        mRedOptionName.setText(mData.getOptions().get(0).optionValue);
        mBlueOptionName.setText(mData.getOptions().get(1).optionValue);

        mRedOptionServerId = mData.getOptions().get(0).optionId;
        mBlueOptionServerId = mData.getOptions().get(1).optionId;

        mRedProgressAnimator = ValueAnimator.ofFloat(0, 1);
        mRedProgressAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
            @Override
            public void onAnimationUpdate(ValueAnimator animation) {
                float value = (float) animation.getAnimatedValue();

                FrameLayout.LayoutParams params = (FrameLayout.LayoutParams) mRedOptionPercentLine.getLayoutParams();
                params.width = (int) (mRedProgressCurWidth + (mRedProgressTgtWidth - mRedProgressCurWidth) * value);
                mRedOptionPercentLine.setLayoutParams(params);
            }
        });
        mRedProgressAnimator.setDuration(200);

        mBlueProgressAnimator = ValueAnimator.ofFloat(0, 1);
        mBlueProgressAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
            @Override
            public void onAnimationUpdate(ValueAnimator animation) {
                float value = (float) animation.getAnimatedValue();

                FrameLayout.LayoutParams params = (FrameLayout.LayoutParams) mBlueOptionPercentLine.getLayoutParams();
                params.width = (int) (mBlueProgressCurWidth + (mBlueProgressTgtWidth - mBlueProgressCurWidth) * value);
                mBlueOptionPercentLine.setLayoutParams(params);
            }
        });
        mBlueProgressAnimator.setDuration(200);

        mVoteData = new VoteData(mContext);
        mVoteData.compose(mData);

        updateView();
    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);

        if(mOptionGp.getVisibility() == View.VISIBLE) {
            if(!mBAnimating) {
                mOptionGpHeight = mOptionGp.getMeasuredHeight();
            }
            mRootHeight = mTitleText.getMeasuredHeight() + mOptionGpHeight + mParticipantsText.getMeasuredHeight() + mTasteStyleHeight;
        } else {
            mRootHeight = mTitleText.getMeasuredHeight() + mDivisionViewHeight + mParticipantsText.getMeasuredHeight() + mTasteStyleHeight;
        }

        if(mBAnimating) {
            mRootHeight = mAnimHeight;
        }

        measureChild(getChildAt(0), MeasureSpec.makeMeasureSpec(widthMeasureSpec, MeasureSpec.EXACTLY), MeasureSpec.makeMeasureSpec(mRootHeight, MeasureSpec.EXACTLY));
        setMeasuredDimension(MeasureSpec.makeMeasureSpec(getMeasuredWidth(), MeasureSpec.EXACTLY), MeasureSpec.makeMeasureSpec(mRootHeight, MeasureSpec.EXACTLY));
    }

    @Override
    protected void onLayout(boolean changed, int l, int t, int r, int b) {
        super.onLayout(changed, l, t, r, b);

        mDivisionViewTop = mTitleText.getMeasuredHeight();
        mDivisionView.layout(BasicMargin, mDivisionViewTop, BasicMargin + mTitleText.getMeasuredWidth(), mDivisionViewTop + mDivisionViewHeight);

        mOptionGpTop =  mTitleText.getMeasuredHeight();
        mOptionGp.layout(BasicMargin, mOptionGpTop, BasicMargin + mOptionGp.getMeasuredWidth(), mOptionGpTop + mOptionGp.getMeasuredHeight());
    }

    @Override
    protected void startExpandAnim() {
        Utils.Log(Utils.LogType.DEBUG, TAG, "startExpandAnim");

        mBAnimating = true;

        final float oriHeight = mRoot.getHeight();
        final float targetHeight = mTitleText.getMeasuredHeight() + mParticipantsText.getMeasuredHeight() + mOptionViewHeight * mData.optionSize() + mTasteStyleHeight;

        final ValueAnimator anim = ValueAnimator.ofFloat(0.0f, 1.0f);
        anim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
            @Override
            public void onAnimationUpdate(ValueAnimator animation) {
                float animValue = (float) animation.getAnimatedValue();

                LayoutParams params = (LayoutParams) mRoot.getLayoutParams();
                params.height = mAnimHeight = (int) (oriHeight + (targetHeight - oriHeight) * animValue);

                mRoot.setLayoutParams(params);
                mFoldText.setAlpha(animValue);
                mOptionGp.setAlpha(animValue);
            }
        });

        anim.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                mBAnimating = false;
                mBExpanded = true;

                // load preset data if not fold default
                if(!mBPreloadDataLoaded)
                    loadPresetData();
            }
        });

        anim.setDuration(400);
        anim.setTarget(mRoot);
        anim.start();

        Utils.Log(Utils.LogType.DEBUG, TAG, "startExpandAnim done");
    }

    @Override
    protected void startCollapseAnim() {
        Utils.Log(Utils.LogType.DEBUG, TAG, "startCollapseAnim");

        mBAnimating = true;

        final float oriHeight = mRoot.getHeight();
        final float targHeight = mTitleText.getMeasuredHeight() + mParticipantsText.getMeasuredHeight() + mDivisionViewHeight + mTasteStyleHeight;

        final ValueAnimator anim = ValueAnimator.ofFloat(0.0f, 1.0f);
        anim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
            @Override
            public void onAnimationUpdate(ValueAnimator animation) {
                float animValue = (float) animation.getAnimatedValue();

                LayoutParams params = (LayoutParams) mRoot.getLayoutParams();
                params.height = mAnimHeight = (int) (oriHeight - (oriHeight - targHeight) * animValue);

                mRoot.setLayoutParams(params);
                mFoldText.setAlpha(animValue);
                mRoot.requestLayout();

                mOptionGp.setAlpha(1 - animValue);
            }
        });

        anim.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                mBAnimating = false;
                mBExpanded = false;
                mOptionGp.setVisibility(View.GONE);
                mDivisionView.setVisibility(View.VISIBLE);
            }
        });

        anim.setDuration(400);
        anim.setTarget(mRoot);
        anim.start();

        Utils.Log(Utils.LogType.DEBUG, TAG, "startCollapseAnim done");
    }

    @Override
    public void onClick(View v) {
        int focusedId = v.getId();
        if(focusedId == mBlueOptionLy.getId()) {
            report(mVoteData.mRid, mVoteData.getReportOptionId(1), mVoteData.getReportCancelId(1), true);
            mVoteData.update(1);
        } else if(focusedId == mRedOptionLy.getId()) {
            report(mVoteData.mRid, mVoteData.getReportOptionId(0), mVoteData.getReportCancelId(0), true);
            mVoteData.update(0);
        }

        updateView();
    }

    private void updateView() {
        mRedOptionPercent = mVoteData.getOptionPercent(mRedOptionServerId);
        mBlueOptionPercent = mVoteData.getOptionPercent(mBlueOptionServerId);

        mRedOptionPercentText.setText(mVoteData.IsFocused() ? String.valueOf(mRedOptionPercent) + "%" : "");
        mBlueOptionPercentText.setText(mVoteData.IsFocused() ? String.valueOf(mBlueOptionPercent) + "%" : "");

        mRedOptionName.setTextSize(mVoteData.IsFocusedIndex(0) ? 13 : 12);
        mRedOptionPercentText.setTextSize(mVoteData.IsFocusedIndex(0) ? 13 : 12);
        mBlueOptionName.setTextSize(mVoteData.IsFocusedIndex(1) ? 13 : 12);
        mBlueOptionPercentText.setTextSize(mVoteData.IsFocusedIndex(1) ? 13 : 12);

        mRedOptionImg.setImageResource(mVoteData.IsFocusedIndex(0) ? R.drawable.icon_thumbreds : R.drawable.icon_thumbred);
        mBlueOptionImg.setImageResource(mVoteData.IsFocusedIndex(1) ? R.drawable.icon_thumblues : R.drawable.icon_thumblue);

        if(mVoteAnimation == null)
            Utils.Log(TAG, "anim null");
        (mVoteData.getUserClickIndex() == 0 ? mRedOptionImg : mBlueOptionImg).startAnimation(mVoteAnimation);

        mRedProgressTgtWidth = mVoteData.IsFocused() ? mOptionGpWidth * mRedOptionPercent / 100 : 0;
        mRedProgressCurWidth = mRedOptionPercentLine.getMeasuredWidth();

        mBlueProgressTgtWidth = mVoteData.IsFocused() ? mOptionGpWidth * mBlueOptionPercent / 100 : 0;
        mBlueProgressCurWidth = mBlueOptionPercentLine.getMeasuredWidth();

        mRedProgressAnimator.start();
        mBlueProgressAnimator.start();

        mParticipantsText.setText(String.valueOf(mVoteData.getTotalCount()) + " 人参加");
    }

    @Override
    public String getType() {
        return TYPE_PK;
    }

    @Override
    public void doNext() {
        Utils.Log(Utils.LogType.DEBUG, TAG, "doNext");
        if(iSender != null)
            iSender.startSync(mData.getRid(), true);
    }

    @Override
    public void syncData(OptionResultModel response) {
        Utils.Log(TAG, "syncData");
        updateView();
    }

    @Override
    public boolean IsPreviewDataSynced() {
        return true;
    }

    @Override
    public void syncPreviewData(ReportResultModel result) {
    }

    /**
     * 在卡片出现动画结束后被调用
     */
    @Override
    protected void loadPresetData() {
        if(!mVoteData.getPresetDataLoad() && mPreselectedIndex >= 0) {
            Utils.Log(TAG, "[loadPresetData] mPreselectedIndex = " + mPreselectedIndex);
            mVoteData.restorePreselectedIndex(mPreselectedIndex);
            updateView();
            mVoteData.setPresetDataLoad(true);
        }
    }
}
